﻿using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Windows.Data;
using Asistente.Model.Representation;

namespace Asistente.Converters
{
    public class IsMantainedEntityConverter : IMultiValueConverter
    {
        //Primer parametro - Application
        //Segundo parametro - Entitdad a eliminar
        public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
        {
            if (values[0] != null && values[1] != null)
            {
                Application application = (Application) values[0]; //Application
                Entity entity = (Entity)values[1]; //Entity

                //Se obtienen todos los casos de uso de Alta baja, ver o modificar.
                foreach (var useCase in GetNewDeleteUpdateView(application.UseCases))
                {
                    if (IsEdited(entity, useCase))
                    {
                        entity.IsMaintained = true; // La entidad es mantenida
                        return true; // En caso de ser editada en alguna alta, baja, modificacion o vista se devuelve true
                    }
                }
                entity.IsMaintained = false; // La entidad no es mantenida
            }

            return false; // En caso de no ser editada en alguna alta, baja, modificacion o vista se devuelve true
        }

        //Verifica si la entidad es editada en useCase
        private bool IsEdited(Entity entity, UseCase useCase)
        {
            foreach (EditablePanel panel in GetFormGrid(useCase)) // Si aparece en un Form o grid como editada, entocnes es editada
            {
                //if(panel.Entity.Equals(entity]))
                if (panel.Entity != null && panel.Entity.Name.Equals(entity.Name)) // Se compara por nombre debido a un probelma al desserializar
                {
                    return true;
                }
            }
            return false;
        }

        //Devuelve los panels del tipo Form o Grid de useCase
        private IEnumerable<EditablePanel> GetFormGrid(UseCase useCase)
        {
            return (from Panel panel in GetPanels(useCase) where panel.GetType() == typeof (Form) || panel.GetType() == typeof (Grid) select panel as EditablePanel).ToList();
        }

        //Devielve todos los panels de useCase
        private IEnumerable<Panel> GetPanels(UseCase useCase)
        {
            List<Panel> panels = new List<Panel>();
            foreach (Screen screen in useCase.Screens)
            {
                panels.AddRange(screen.Panels); // Los paneles de cada pantalla

                foreach (MasterDetail masterDetal in screen.MasterDetails)
                {
                    panels.Add(masterDetal.Master); // Se agrega el panel master
                    panels.AddRange(masterDetal.Details); // Se agrega el panel detail
                }
            }

            return panels;


        }

        //Devuelve los casos de uso de alta baja modificacion o vista
        private IEnumerable<UseCase> GetNewDeleteUpdateView(IEnumerable<UseCase> useCases)
        {
            return useCases.Where(useCase => useCase.Pattern == UseCasePattern.New || useCase.Pattern == UseCasePattern.LogicDelete || useCase.Pattern == UseCasePattern.PhysicalDelete || useCase.Pattern == UseCasePattern.View || useCase.Pattern == UseCasePattern.Update).ToList();
        }

        public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }

}